/**
 * FireFly (2011)
 */
package com.firefly.kernel;

import com.firefly.kernel.spi.bootstrap.IKernelInitializer;
import com.firefly.kernel.spi.config.IKernelConfig;
import com.firefly.logging.Logger;

/**
 * 工厂方法构件核心
 * 
 * @version 1.0 2011-1-2
 * @author <a herf="lexloo@gmail.com">lexloo</a>
 * @since FireFly 1.0
 */
public enum KernelFactory {
	INSTANCE;

	/** The logger */
	private final Logger log = Logger.getLogger(KernelFactory.class);

	KernelFactory() {
	}

	/**
	 * 通过配置创建核心实例
	 * 
	 * @param cfg
	 *            配置
	 * @return 核心实例
	 */
	public static Kernel newKernel(IKernelConfig cfg) {
		return INSTANCE.assembleNewKernel(cfg);
	}

	private Kernel assembleNewKernel(IKernelConfig cfg) throws RuntimeException {
		long begin = 0;

		log.info("开始核心构建...");
		begin = System.currentTimeMillis();

		Kernel kernel = createKernel();
		log.trace("使用核心:%s", kernel);
		log.trace("使用配置:%s", cfg);
		log.trace("配置核心");
		configureKernel(kernel, cfg);
		
		IKernelInitializer initializer = createKernelInitializer(cfg);
		log.trace("使用核心初始化构造器:%s", initializer);

		initializeKernel(kernel, initializer);
		log.trace("核心实例初始化");

		log.debug("完成核心构造，使用时间：%1d毫秒", (System.currentTimeMillis() - begin));
		return kernel;
	}

	/**
	 * 创建核心对象
	 * 
	 * @return 核心对象
	 */
	private Kernel createKernel() {
		return new Kernel();
	}

	private IKernelInitializer createKernelInitializer(IKernelConfig config) {
		try {
			return config.createKernelInitializer();
		} catch (Throwable t) {
			throw new RuntimeException("不能通过核心配置构建核心初始化构造器", t);
		}
	}

	private void configureKernel(Kernel kernel, IKernelConfig cfg) {
		kernel.setConfig(cfg);
		try {
			cfg.setKernel(kernel);
		} catch (Throwable t) {
			throw new RuntimeException("不能更新核心的配置信息", t);
		}
	}

	private void initializeKernel(Kernel kernel, IKernelInitializer initializer) {
		try {
			initializer.initKernel(kernel);
		} catch (Throwable t) {
			throw new RuntimeException("不能正确初始化核心", t);
		}
	}
}
